package com.lzb.musicplayer.audio;

import android.content.Context;
import android.media.audiofx.BassBoost;
import android.media.audiofx.Equalizer;
import android.media.audiofx.Virtualizer;
import android.net.Uri;
import android.os.Handler;
import android.text.TextUtils;
import android.util.Log;

import androidx.annotation.OptIn;
import androidx.media3.common.MediaItem;
import androidx.media3.common.PlaybackParameters;
import androidx.media3.common.Player;
import androidx.media3.common.util.UnstableApi;
import androidx.media3.exoplayer.ExoPlayer;


import com.lzb.musicplayer.bean.MusicFile;
import com.lzb.musicplayer.bean.MusicInfo;
import com.lzb.musicplayer.utils.AppSpUtils;
import com.lzb.musicplayer.utils.SpUtils;
import com.lzb.musicplayer.view.ReverbManager;
import com.lzb.basic.utils.SPUtil;
import com.lzb.musicplayer.Content;
import androidx.media3.common.AudioAttributes;
import androidx.media3.common.C;

import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Random;

// 1. 创建全局播放管理器（单例）
public class AudioPlayerManager implements Player.Listener {
    private static AudioPlayerManager instance;
    private final Equalizer equalizer;
    private final MusicInfo musicInfo;
    private ExoPlayer exoPlayer;
    private List<MusicFile> playList = new ArrayList<>();
    private int currentIndex = 0;
    private List<PlaybackStateListener> listeners = new ArrayList<>();
    
    // 音频设置
    private int fadeDuration = 7000; // 默认淡入淡出时长（毫秒）
    private boolean seamlessPlayback = false; // 无缝播放
    private boolean alwaysPlay = false; // 始终播放模式
    private ReverbManager reverbManager;
    private BassBoost bassBoost;
    private Virtualizer virtualizer;
    // 进度更新相关
    private Handler updateHandler = new Handler();
    private final Runnable updateRunnable = new Runnable() {
        @Override
        public void run() {
            updateProgressDisplay();
            updateHandler.postDelayed(this, 200); // 每秒更新一次
        }
    };


    @OptIn(markerClass = UnstableApi.class)
    private AudioPlayerManager(Context context) {
        exoPlayer = new ExoPlayer.Builder(context).build();
        exoPlayer.addListener(this);
        
        // 从SPUtil加载音频设置
        loadAudioSettings(context);
        
        // 安全初始化Equalizer
        Equalizer tempEqualizer = null;
        try {
            tempEqualizer = new Equalizer(0, exoPlayer.getAudioSessionId());
            tempEqualizer.setEnabled(true);
            Log.d("AudioPlayerManager", "Equalizer initialized successfully");
        } catch (RuntimeException e) {
            Log.e("AudioPlayerManager", "Failed to initialize Equalizer: " + e.getMessage());
            tempEqualizer = null;
        }
        equalizer = tempEqualizer;
        
        // 安全初始化混响效果
        try {
            reverbManager = new ReverbManager(exoPlayer.getAudioSessionId());
            Log.d("AudioPlayerManager", "ReverbManager initialized successfully");
        } catch (Exception e) {
            Log.e("AudioPlayerManager", "Failed to initialize ReverbManager: " + e.getMessage());
            reverbManager = null;
        }
        
        // 安全初始化低音增强
        BassBoost tempBassBoost = null;
        try {
            tempBassBoost = new BassBoost(0, exoPlayer.getAudioSessionId());
            tempBassBoost.setEnabled(true);
            Log.d("AudioPlayerManager", "BassBoost initialized successfully");
        } catch (Exception e) {
            Log.e("AudioPlayerManager", "Failed to initialize BassBoost: " + e.getMessage());
            tempBassBoost = null;
        }
        bassBoost = tempBassBoost;
        
        // 安全初始化Virtualizer
        Virtualizer tempVirtualizer = null;
        try {
            tempVirtualizer = new Virtualizer(0, exoPlayer.getAudioSessionId());
            tempVirtualizer.setEnabled(true);
            Log.d("AudioPlayerManager", "Virtualizer initialized successfully");
        } catch (Exception e) {
            Log.e("AudioPlayerManager", "Failed to initialize Virtualizer: " + e.getMessage());
            tempVirtualizer = null;
        }
        virtualizer = tempVirtualizer;
        
        int type = SpUtils.getInstance().getInt("openType", 0);
        if (type == 1 && equalizer != null) {
            // 开启均衡器（只有在equalizer初始化成功时）
            setShowData();
        }
        musicInfo = new MusicInfo();
        float speed = SpUtils.getInstance().getFloat("speed", 1);
        float pitch = SpUtils.getInstance().getFloat("pitch", 1);
        setPlaybackParameters(speed, pitch);
    }
    
    /**
     * 从SPUtil加载音频设置
     */
    private void loadAudioSettings(Context context) {
        // 加载淡入淡出时长设置
        fadeDuration = SPUtil.getInt(context, Content.fadeDuration, 7) * 1000; // 转换为毫秒
        
        // 加载无缝播放设置
        seamlessPlayback = SPUtil.getBoolean(context, Content.isOpenSeamless, false);
        
        // 加载始终播放设置
        alwaysPlay = SPUtil.getBoolean(context, Content.isOpenAlways, false);
        
        // 如果启用始终播放，设置音频属性以支持混音
        if (alwaysPlay) {
            exoPlayer.setAudioAttributes(new AudioAttributes.Builder()
                    .setUsage(C.USAGE_MEDIA)
                    .setContentType(C.AUDIO_CONTENT_TYPE_MUSIC)
                    .build(), true); // 第二个参数表示是否处理音频焦点
        }
        
        Log.d("AudioPlayerManager", "Audio settings loaded - FadeDuration: " + (fadeDuration/1000) + "s, " +
                "Seamless: " + seamlessPlayback + ", AlwaysPlay: " + alwaysPlay);
    }


    // 顺序播放下一首
    private void playNextInOrder() {
        if (currentIndex < playList.size() - 1) {
            currentIndex++;
            exoPlayer.seekTo(currentIndex, 0);
        } else {
            exoPlayer.stop(); // 播放列表结束
        }
    }

    // 单曲循环
    private void replayCurrent() {
        exoPlayer.seekTo(currentIndex, 0);
        exoPlayer.setPlayWhenReady(true);
    }

    // 随机播放
    private void playRandom() {
        int newIndex = new Random().nextInt(playList.size());
        currentIndex = newIndex;
        exoPlayer.seekTo(currentIndex, 0);
        exoPlayer.setPlayWhenReady(true);
    }

    public static synchronized AudioPlayerManager getInstance(Context context) {
        if (instance == null) {
            instance = new AudioPlayerManager(context.getApplicationContext());
        }
        return instance;
    }

    // 2. 核心播放方法
    public void play(List<MusicFile> list, int position) {
        if (!playList.isEmpty()) {
            if (!playList.equals(list)) {
                playList.clear();
                playList.addAll(list);
                currentIndex = position;
                prepareAndPlay();
            }
        } else {
            playList.clear();
            playList.addAll(list);
            currentIndex = position;
            prepareAndPlay();
        }
        notifyStateChanged(isPlaying());
    }

    public void play(List<MusicFile> list) {
        if (playList != null) {
            playList.clear();
            playList.addAll(list);
        }
    }

    public void clean() {
        if (playList != null) {
            playList.clear();
        }
    }

    public List<MusicFile> getList() {
        return playList;
    }

    public void setPlaybackParameters(float seek, float seek1) {
        exoPlayer.setPlaybackParameters(
                new PlaybackParameters(seek, seek1));

    }

    public float getSpeed() {
        if (exoPlayer.getPlaybackParameters() != null) {
            return exoPlayer.getPlaybackParameters().speed;
        }
        return 1;
    }

    public float getPitch() {
        if (exoPlayer.getPlaybackParameters() != null) {
            return exoPlayer.getPlaybackParameters().pitch;
        }
        return 1;
    }

    private void prepareAndPlay() {
        if (playList.isEmpty()) return;
        MediaItem mediaItem = MediaItem.fromUri(Uri.parse(playList.get(currentIndex).getPath()));
        exoPlayer.setMediaItem(mediaItem);
        exoPlayer.prepare();
        notifyTrackChanged();
    }

    public void prepareAndPlay(int position) {
        if (playList.isEmpty()) return;
        currentIndex = position;
        MediaItem mediaItem = MediaItem.fromUri(Uri.parse(playList.get(position).getPath()));
        exoPlayer.setMediaItem(mediaItem);
     /*   if (position<playList.size()){
            MediaItem mediaItem = MediaItem.fromUri(Uri.parse(playList.get(position).getPath()));
            exoPlayer.setMediaItem(mediaItem);
        }else {
            currentIndex=0;
            MediaItem mediaItem = MediaItem.fromUri(Uri.parse(playList.get(0).getPath()));
            exoPlayer.setMediaItem(mediaItem);
        }*/

        exoPlayer.prepare();
        notifyTrackChanged();
    }

    public void pause() {
        if (isPlaying()) {
            exoPlayer.pause();
        }

        stopProgressUpdates();
        notifyStateChanged(false);
    }

    // 3. 播放控制方法
    public void togglePlayback() {
        if (exoPlayer.isPlaying()) {
            exoPlayer.pause();
            stopProgressUpdates();
            notifyStateChanged(false);
        } else {
            exoPlayer.play();
            startProgressUpdates();
            notifyStateChanged(true);
            //记录播放次数
            List<MusicFile> list = SpUtils.getInstance().getList("listmore");
            List<MusicFile> listzj = SpUtils.getInstance().getList("listzj");
            if (list != null && getCurrentTrack() != null) {
                listzj.clear();
                list.add(getCurrentTrack());
                listzj.add(getCurrentTrack());
                try {
                    SpUtils.getInstance().putList("listmore", list);
                    SpUtils.getInstance().putList("listzj", listzj);
                } catch (Exception e) {
                    Log.e("111", e.getMessage());
                }

            }
            List<MusicFile> listRecord = AppSpUtils.getRecordList();
            if (listRecord == null) listRecord = new ArrayList<>();
            if (!listRecord.contains(getCurrentTrack())) {
                listRecord.add(getCurrentTrack());
            }
            AppSpUtils.saveRecordList(listRecord);
        }

    }

    public void seekTo(long position) {
        exoPlayer.seekTo(position);
    }

    public void playNext() {
        currentIndex = (currentIndex + 1) % playList.size();
        prepareAndPlay();
    }

    public void playPrevious() {
        currentIndex = (currentIndex - 1 + playList.size()) % playList.size();
        prepareAndPlay();
    }

    // 4. 状态监听回调
    @Override
    public void onPlaybackStateChanged(int state) {
        if (state == Player.STATE_ENDED) {
            handlePlaybackEnded();
        } else if (state == Player.STATE_READY) {
            restorePlay();
        }
        for (PlaybackStateListener listener : listeners) {
            listener.onPlaybackStateChanged(state);
        }
    }


    private void setShowData() {
        if (SpUtils.getInstance().getInt("openType", 0) == 1) {
            //设置风格数据
            int fgSeek1 = SpUtils.getInstance().getInt("fgSeek1", 0);
            // 设置均衡器参数（转换为毫贝单位）
            setBandLevel((short) 0, (short) ((fgSeek1 - 15) * 100));
            int fgSeek2 = SpUtils.getInstance().getInt("fgSeek2", 0);
            // 设置均衡器参数（转换为毫贝单位）
            setBandLevel((short) 1, (short) ((fgSeek2 - 15) * 100));
            int fgSeek3 = SpUtils.getInstance().getInt("fgSeek3", 0);
            // 设置均衡器参数（转换为毫贝单位）
            setBandLevel((short) 2, (short) ((fgSeek3 - 15) * 100));
            int fgSeek4 = SpUtils.getInstance().getInt("fgSeek4", 0);
            // 设置均衡器参数（转换为毫贝单位）
            setBandLevel((short) 3, (short) ((fgSeek4 - 15) * 100));
            int fgSeek5 = SpUtils.getInstance().getInt("fgSeek5", 0);
            // 设置均衡器参数（转换为毫贝单位）
            setBandLevel((short) 4, (short) ((fgSeek5 - 15) * 100));

            //混响设置
            String string = SpUtils.getInstance().getString("hxTxt", "关闭");
            if (string.equals("关闭")) {
                setReverbType(ReverbManager.ReverbType.NONE);
            } else if (string.equals("小型房间")) {
                setReverbType(ReverbManager.ReverbType.SMALL_ROOM);
            } else if (string.equals("中型房间")) {
                setReverbType(ReverbManager.ReverbType.MEDIUM_ROOM);
            } else if (string.equals("大型房间")) {
                setReverbType(ReverbManager.ReverbType.LARGE_ROOM);
            } else if (string.equals("中型音乐厅")) {
                setReverbType(ReverbManager.ReverbType.MEDIUM_HALL);
            } else if (string.equals("大型音乐厅")) {
                setReverbType(ReverbManager.ReverbType.LARGE_HALL);
            } else if (string.equals("板式混响")) {
                setReverbType(ReverbManager.ReverbType.PLATE);
            }
            //低音增强设置
            int dyzq = SpUtils.getInstance().getInt("dyzq", 0);
            setStrength(dyzq);
            //音场增强
            int yczq = SpUtils.getInstance().getInt("yczq", 0);
            setStrengthVirtualizer((short) yczq);
            //音量增强
            int ylzq = SpUtils.getInstance().getInt("ylzq", 100);
            setVolume(ylzq / 100f);
        }
    }

    public void setStrengthVirtualizer(int progress) {
        if (virtualizer != null) {
            try {
                virtualizer.setStrength((short) progress);
                Log.d("AudioPlayerManager", "Set Virtualizer strength: " + progress);
            } catch (Exception e) {
                Log.e("AudioPlayerManager", "Failed to set Virtualizer strength: " + e.getMessage());
            }
        } else {
            Log.w("AudioPlayerManager", "Cannot set Virtualizer strength - Virtualizer not initialized");
        }
    }

    public void setStrength(int progress) {
        if (bassBoost != null) {
            try {
                bassBoost.setStrength((short) progress);
                Log.d("AudioPlayerManager", "Set BassBoost strength: " + progress);
            } catch (Exception e) {
                Log.e("AudioPlayerManager", "Failed to set BassBoost strength: " + e.getMessage());
            }
        } else {
            Log.w("AudioPlayerManager", "Cannot set BassBoost strength - BassBoost not initialized");
        }
    }

    public void setReverbType(ReverbManager.ReverbType aa) {
        if (reverbManager != null) {
            try {
                reverbManager.setReverbType(aa);
                Log.d("AudioPlayerManager", "Set Reverb type: " + aa);
            } catch (Exception e) {
                Log.e("AudioPlayerManager", "Failed to set Reverb type: " + e.getMessage());
            }
        } else {
            Log.w("AudioPlayerManager", "Cannot set Reverb type - ReverbManager not initialized");
        }
    }

    public void setBandLevel(short band, short level) {
        if (equalizer != null) {
            try {
                equalizer.setBandLevel(band, level);// 0 1=-1200   2=700 3=1500 4=1500
                Log.d("AudioPlayerManager", "Set Equalizer band level - Band: " + band + ", Level: " + level);
            } catch (Exception e) {
                Log.e("AudioPlayerManager", "Failed to set Equalizer band level: " + e.getMessage());
            }
        } else {
            Log.w("AudioPlayerManager", "Cannot set Equalizer band level - Equalizer not initialized");
        }
    }

    public void setVolume(float volume) {
        exoPlayer.setVolume(volume);
    }

    public enum PlaybackMode {
        NORMAL,      // 顺序播放
        REPEAT_ONE,  // 单曲循环
        SHUFFLE      // 随机播放
    }

    private PlaybackMode currentMode = PlaybackMode.NORMAL;

    // 设置播放模式
    public void setPlaybackMode(PlaybackMode mode) {
        currentMode = mode;
        if (mode == PlaybackMode.SHUFFLE) {
            Collections.shuffle(playList); // 随机打乱列表
        }
    }

    @OptIn(markerClass = UnstableApi.class)
    public int getAudioSessionId() {
        int audioSessionId = exoPlayer.getAudioSessionId();
        return audioSessionId;
    }

    // 处理播放结束
    private void handlePlaybackEnded() {
        switch (currentMode) {
            case NORMAL:
                playNextInOrder();
                break;
            case REPEAT_ONE:
                replayCurrent();
                break;
            case SHUFFLE:
                playRandom();
                break;
        }
    }

    public void stopProgressUpdates() {
        updateHandler.removeCallbacks(updateRunnable);
    }

    public void startProgressUpdates() {
        updateHandler.removeCallbacks(updateRunnable);
        updateProgressDisplay();
        updateHandler.post(updateRunnable);
    }

    //倒计时更新进度
    private void updateProgressDisplay() {
        int bcType = SpUtils.getInstance().getInt("bcType", 0);
        if (bcType == 1) {
            //保存长音频进度
            long duration = exoPlayer.getDuration();
            if (duration >= 1 * 60 * 1000) { // 10分钟以上音频

                if (musicInfo != null) {
                    if (!(getCurrentTrack().getPath().equals(musicInfo.getPath()) && exoPlayer.getCurrentPosition() == musicInfo.getCurrentPosition())) {
                        if (!TextUtils.isEmpty(getCurrentTrack().getPath())) {
                            musicInfo.setPath(getCurrentTrack().getPath());
                            musicInfo.setCurrentPosition(exoPlayer.getCurrentPosition());
                            musicInfo.setDuration(exoPlayer.getDuration());
                        }

                        List<MusicInfo> listBc = SpUtils.getInstance().getListBc("listBc");
                        addOrUpdate(listBc, musicInfo);
                        SpUtils.getInstance().putListBc("listBc", listBc);
                    }

                }
            }
        }
        notifyProgress(exoPlayer.getCurrentPosition(), exoPlayer.getDuration());
    }

    public static void addOrUpdate(List<MusicInfo> list, MusicInfo musicInfo) {
        for (MusicInfo bean : list) {
            // 根据id判断是否为同一对象
            if (bean.getPath().equals(musicInfo.getPath())) {
                bean.setPath(musicInfo.getPath());
                bean.setDuration(musicInfo.getDuration());
                bean.setCurrentPosition(musicInfo.getCurrentPosition());
                return;
            }
        }
        // 未找到时添加新对象
        list.add(musicInfo);
    }

    public MusicInfo musicInfo1 = null;

    public void restorePlay() {
        int bcType = SpUtils.getInstance().getInt("bcType", 0);
        if (bcType == 1) {
            if (exoPlayer == null) return;
            if (musicInfo1 != null && !TextUtils.isEmpty(musicInfo1.getPath())) {
                if (getCurrentTrack() != null && getCurrentTrack().getPath() != null && musicInfo1.getPath().equals(getCurrentTrack().getPath())) {
                    return;
                }
            }
            List<MusicInfo> listBc = SpUtils.getInstance().getListBc("listBc");
            for (int i = 0; i < listBc.size(); i++) {
                if (getCurrentTrack() != null && listBc.get(i).getPath().equals(getCurrentTrack().getPath())) {
                    musicInfo1 = listBc.get(i);
                    break;
                }
            }
            if (musicInfo1 != null) {
                long savedPosition = musicInfo1.getCurrentPosition();
                long savedDuration = musicInfo1.getDuration();
                long currentDuration = exoPlayer.getDuration();
                // 有效性校验
                if (savedPosition > 0 && savedDuration > 0) {
                    // 检测音频是否被修改（时长差异超过10%）
                    if (Math.abs(currentDuration - savedDuration) > savedDuration * 0.1) {
                        clearSavedPosition();
                        return;
                    }
                    // 安全跳转位置
                    long safePosition = Math.min(savedPosition, currentDuration - 1000);
                    exoPlayer.seekTo(safePosition);
                }
            }
        }
    }

    private void clearSavedPosition() {
        List<MusicInfo> listBc = SpUtils.getInstance().getListBc("listBc");
        for (int i = 0; i < listBc.size(); i++) {
            if (listBc.get(i).getPath().equals(musicInfo.getPath())) {
                listBc.remove(i);
                break;
            }
        }
    }

    // 5. 观察者模式实现
    public interface PlaybackStateListener {
        void onPlaybackStateChanged(boolean isPlaying);

        void onPlaybackStateChanged(int state);

        void onProgressUpdated(long position, long duration);

        void onTrackChanged(MusicFile currentTrack);
    }

    public void addListener(PlaybackStateListener listener) {
        if (!listeners.contains(listener)) {
            listeners.add(listener);
        }
    }

    public void removeListener(PlaybackStateListener listener) {
        listeners.remove(listener);
    }

    private void notifyStateChanged(boolean isPlaying) {
        if (getCurrentTrack() != null) {
            getCurrentTrack().setPlay(isPlaying);
        }
        for (PlaybackStateListener listener : listeners) {
            listener.onPlaybackStateChanged(isPlaying);
        }
    }

    private void notifyProgress(long position, long duration) {
        for (PlaybackStateListener listener : listeners) {
            listener.onProgressUpdated(position, duration);
        }
    }

    private void notifyTrackChanged() {
        for (PlaybackStateListener listener : listeners) {
            listener.onTrackChanged(getCurrentTrack());
        }
    }

    // 6. 状态获取方法
    public MusicFile getCurrentTrack() {
        return playList.isEmpty() ? null : playList.get(currentIndex);
    }

    public boolean isPlaying() {
        return exoPlayer.isPlaying();
    }

    public long getCurrentPosition() {
        return exoPlayer.getCurrentPosition();
    }

    public long getDuration() {
        return exoPlayer.getDuration();
    }
    
    // 音频设置获取方法
    public int getFadeDuration() {
        return fadeDuration / 1000; // 转换为秒
    }
    
    public boolean isSeamlessPlayback() {
        return seamlessPlayback;
    }
    
    public boolean isAlwaysPlay() {
        return alwaysPlay;
    }

    public void release() {
        exoPlayer.release();
        listeners.clear();
        instance = null;
    }
}

